<script setup lang="ts">
import { onMounted } from "vue";

let selection: Selection | null = null;

onMounted(() => {
  document.addEventListener("selectionchange", () => {
    const innerSelection = window.getSelection();

    const isInEditor =
      innerSelection?.focusNode &&
      document
        .querySelector(".editor-content")
        ?.contains(innerSelection?.focusNode);

    console.log(
      "🚀 ~ document.addEventListener ~ innerSelection?.focusNode:",
      innerSelection,
      innerSelection?.focusNode,
      document.querySelector(".editor-content")
    );

    if (!isInEditor) {
      return;
    }
    selection = innerSelection;

    console.log("🚀 ~ document.addEventListener ~ isInEditor:", isInEditor);
    console.log("🚀 ~ editorContent.addEventListener ~ selection:", selection);
    if (!selection) return;
    const range = selection.getRangeAt(0);
    console.log("🚀 ~ selectionchange ~ range:", range);
  });
});

// 检查当前选区是否已被包装
// function isWrapped(range, command) {
//   let container = range.commonAncestorContainer;
//   if (container.nodeType === Node.TEXT_NODE) {
//     container = container.parentNode;
//   }

//   switch (command) {
//     case "bold":
//       return container.nodeName === "B";
//     case "italic":
//       return container.nodeName === "I";
//     case "underline":
//       return container.nodeName === "U";
//     default:
//       return false;
//   }
// }
// 检查当前选区是否已被包装
function isWrapped(range, command) {
  let container = range.commonAncestorContainer;

  if (container.nodeType === Node.TEXT_NODE) {
    container = container.parentNode;
  }

  // 遍历父节点，检查是否有指定格式的节点
  while (container && container !== document) {
    switch (command) {
      case "bold":
        if (container.nodeName === "B" || container.nodeName === "STRONG")
          return true;
        break;
      case "italic":
        if (container.nodeName === "I" || container.nodeName === "EM")
          return true;
        break;
      case "underline":
        if (container.nodeName === "U") return true;
        break;
      case "color":
        if (container.nodeName === "SPAN" && container.style.color) return true;
        break;
      default:
        return false;
    }
    container = container.parentNode;
  }
  return false;
}

// 移除包装节点
// function unwrap(range, command) {
//   let container = range.commonAncestorContainer;
//   if (container.nodeType === Node.TEXT_NODE) {
//     container = container.parentNode;
//   }

//   if (
//     (command === "bold" && container.nodeName === "B") ||
//     (command === "italic" && container.nodeName === "I") ||
//     (command === "underline" && container.nodeName === "U")
//   ) {
//     const parent = container.parentNode;
//     while (container.firstChild) {
//       parent.insertBefore(container.firstChild, container);
//     }
//     parent.removeChild(container);
//   }
// }
// 移除包装节点
function unwrap(range, command) {
  let container = range.commonAncestorContainer;
  if (container.nodeType === Node.TEXT_NODE) {
    container = container.parentNode;
  }

  // 使用递归方式移除指定格式节点
  function unwrapNode(node) {
    const parent = node.parentNode;
    while (node.firstChild) {
      parent.insertBefore(node.firstChild, node); // 将所有子节点插入到父节点中
    }
    parent.removeChild(node);
  }

  // 检查和移除目标格式的节点
  let current = container;
  while (current && current !== document) {
    if (
      (command === "bold" &&
        (current.nodeName === "B" || current.nodeName === "STRONG")) ||
      (command === "italic" &&
        (current.nodeName === "I" || current.nodeName === "EM")) ||
      (command === "underline" && current.nodeName === "U") ||
      (command === "color" &&
        current.nodeName === "SPAN" &&
        current.style.color)
    ) {
      unwrapNode(current);
      break;
    }
    current = current.parentNode;
  }
}

// function exec(command: string, extra?: any) {
//   if (!selection) return;
//   // 清除所有选取
//   // selection.removeAllRanges();
//   const range = selection.getRangeAt(0);
//   // 处理
//   const selectedText = range.extractContents();
//   // const selectedText = range.cloneContents();
//   console.log("🚀 ~ exec ~ selection:", selection);
//   console.log("🚀 ~ exec ~ range:", range);
//   console.log("🚀 ~ exec ~ selectedText:", selectedText, range.cloneContents());

//   // 将选中内容放置到容器
//   let wrapper;

//   const isContentWrapped = isWrapped(range, command);
//   console.log("🚀 ~ exec ~ isContentWrapped:", isContentWrapped);

//   if (isContentWrapped) {
//     unwrap(range, command);
//     return;
//   }

//   switch (command) {
//     case "bold":
//       wrapper = document.createElement("strong");
//       break;
//     case "italic":
//       wrapper = document.createElement("em");
//       break;
//     case "underline":
//       wrapper = document.createElement("u");
//       break;
//     case "color":
//       wrapper = document.createElement("span");
//       wrapper.style.color = extra.color;
//       break;
//     default:
//       break;
//   }

//   if (!wrapper) return;

//   wrapper.appendChild(selectedText);
//   range.insertNode(wrapper);

//   // 看是否需要更新光标位置
// }
function format(command: string, extra?: any) {
  if (!selection) return;

  const range = selection.getRangeAt(0);
  const isContentWrapped = isWrapped(range, command);

  if (isContentWrapped) {
    unwrap(range, command); // 如果已被包裹，解除格式
    return;
  }

  // 如果没有被包裹，则应用新格式
  let wrapper;
  switch (command) {
    case "bold":
      wrapper = document.createElement("strong");
      break;
    case "italic":
      wrapper = document.createElement("em");
      break;
    case "underline":
      wrapper = document.createElement("u");
      break;
    case "color":
      wrapper = document.createElement("span");
      wrapper.style.color = extra.color;
      break;
    default:
      break;
  }

  if (!wrapper) return;

  const selectedText = range.extractContents();
  wrapper.appendChild(selectedText);
  range.insertNode(wrapper);

  // 将光标放在新节点后面
  const newRange = document.createRange();
  // newRange.setStartAfter(wrapper);
  newRange.selectNodeContents(wrapper);
  newRange.collapse(true);

  selection.removeAllRanges();
  selection.addRange(newRange);
}
</script>

<template>
  <!-- <input /> -->
  <!-- <textarea></textarea> -->
  <button @click="format('bold')">加粗</button>
  <button @click="format('italic')">斜体</button>
  <button @click="format('underline')">下划线</button>
  <div class="editor-container">
    <div class="editor-content" contenteditable="true">
      <p>妙码学院，合一</p>
    </div>
    <div class="cursor" ref="cursor"></div>
  </div>
</template>

<style scoped>
.editor-container {
  position: relative;
}
.editor-content {
  width: 100%;
  border: 1px solid #ccc;
  min-height: 200px;
  padding: 10px;
}
.cursor {
  opacity: 0;
  position: absolute;
  width: 1px;
  height: 20px;
  background-color: #333;
}
</style>
